# Define your item pipelines here
#
# Don't forget to add your pipeline to the ITEM_PIPELINES setting
# See: https://docs.scrapy.org/en/latest/topics/item-pipeline.html


# useful for handling different item types with a single interface
import os
import requests
from itemadapter import ItemAdapter
from moviepy.editor import VideoFileClip, AudioFileClip, CompositeVideoClip


class BilibiliPipeline:
    def process_item(self, item, spider):
        # 定义文件存放路径
        DOWNLOAD_DIR = '哔哩哔哩'
        if not os.path.exists(DOWNLOAD_DIR):
            os.mkdir(DOWNLOAD_DIR)
        video_url = item.get('video_url')
        video_filename = "{}\{}.mp4".format(DOWNLOAD_DIR, item.get('name'))
        # 下载视频文件
        self.download_item(video_url, video_filename)

        audio_url = item.get('audio_url')
        audio_filename = "{}\{}.mp3".format(DOWNLOAD_DIR, item.get('name'))
        # 下载音频文件
        self.download_item(audio_url, audio_filename)

        # 合并音视频文件
        self.mergeVideoAudio(item.get('name'), video_filename, audio_filename)
        return item
    def download_item(self, url, filename):
        header = {
            "Accept": "text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.7",
            "Accept-Encoding": "gzip, deflate, br, zstd",
            "Accept-Language": "zh-CN,zh;q=0.9",
            "Cache-Control": "max-age=0",
            "Cookie": "buvid3=071684C9-A4E3-3684-AAFC-EE35227A4FAC81284infoc; b_nut=1717225581; _uuid=BAC310E53-941A-5C6A-E69D-6F6268F288A591178infoc; buvid4=A488BC6C-469C-8304-C91D-DA32920A13B993505-024060107-y91BN2WedSjJMfOqGatQkA%3D%3D; buvid_fp=87ebc9973f253dcd5a1071118687f2d3; DedeUserID=506537472; DedeUserID__ckMd5=6f456d991619f8ed; SESSDATA=00226db8%2C1733907942%2C89cd9%2A62CjDpci4_dPiV4X8eNwYrTMV0VbEMivePNYbaLCkHG9sAez1ynYdUcK36eHodqCQxsAwSVl9Ic1NrU2dyZWZORGpaVUZfTGV2ekJ6STY2SnBELVlmT3JtRlA2OURtMVNfQk4zMlliU2wzX2t1eldYTDNuckpoTGNYQjZVc21HUmFHVkFSMERLT3V3IIEC; bili_jct=3cce1e68624769dc8c887aecf77004e7; CURRENT_FNVAL=4048; bili_ticket=eyJhbGciOiJIUzI1NiIsImtpZCI6InMwMyIsInR5cCI6IkpXVCJ9.eyJleHAiOjE3MTg2NzQ4NjgsImlhdCI6MTcxODQxNTYwOCwicGx0IjotMX0.hYFEiInmMLjMsRXSilmFpoa_F8Mmz0h13TveAOgUhVE; bili_ticket_expires=1718674808; rpdid=|(k|k~~~Rm~~0J'u~u)RulY)Y; b_lsid=D9DF8FED_19019BAA4BF; sid=8hkc8f1f",
            "Priority": "u=0, i",
            "Referer": "https://space.bilibili.com/34579852/video",
            "Sec-Ch-Ua": "\"Not/A)Brand\";v=\"8\", \"Chromium\";v=\"126\", \"Google Chrome\";v=\"126\"",
            "Sec-Ch-Ua-Mobile": "?0",
            "Sec-Ch-Ua-Platform": "\"Windows\"",
            "Sec-Fetch-Dest": "document",
            "Sec-Fetch-Mode": "navigate",
            "Sec-Fetch-Site": "same-origin",
            "Sec-Fetch-User": "?1",
            "Upgrade-Insecure-Requests": "1",
            "User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/126.0.0.0 Safari/537.36"
        }
        try:
            responses = requests.get(url=url, headers=header)
            responses.raise_for_status()
            with open(filename, 'wb') as file:
                file.write(responses.content)
        except Exception as e:
            print(e)

    def mergeVideoAudio(self, name, video_filename, audio_filename):
        # 加载视频和音频文件
        video_clip = VideoFileClip(video_filename)
        audio_clip = AudioFileClip(audio_filename)

        # 设置音频和视频的长度一致（取两者中较短的一个）
        final_duration = min(video_clip.duration, audio_clip.duration)
        video_clip = video_clip.set_duration(final_duration)
        audio_clip = audio_clip.set_duration(final_duration)

        # 合并视频和音频
        final_clip = CompositeVideoClip([video_clip.set_audio(audio_clip)])

        if not os.path.exists('新哔哩哔哩'):
            os.mkdir('新哔哩哔哩')
        # 输出文件路径
        output_file = f'新哔哩哔哩/{name}.mp4'
        # 写入输出文件
        final_clip.write_videofile(output_file, codec='libx264', audio_codec='aac')